package net.gazhi.delonix.mvn;

import java.io.BufferedReader;
import java.io.File;
import java.io.InputStreamReader;
import java.sql.Timestamp;
import java.util.Properties;

import org.apache.maven.plugin.AbstractMojo;
import org.apache.maven.plugin.MojoExecutionException;
import org.apache.maven.plugins.annotations.Mojo;
import org.apache.maven.plugins.annotations.Parameter;
import org.apache.maven.project.MavenProject;

/**
 * 遍历 <b>src/main/webapp/static</b> 下的文件，获取最近的修改时间，并设置为属性：static_last_modified<br>
 * <br>
 * 这个插件的目的是为了实现： js 和 css 等静态文件修改后，强制浏览器重新请求静态资源<br>
 * <br>
 * <b>示例 pom.xml</b>
 * 
 * <pre>
 * &lt;build>
 * 
 * &lt;resources>
 *   &lt;resource>
 *     &lt;directory>src/main/resources&lt;/directory>
 *     &lt;excludes>
 *       &lt;exclude>jsp/inc/taglib.jsp&lt;/exclude>
 *     &lt;/excludes>
 *   &lt;/resource>
 *   &lt;resource>
 *     &lt;directory>src/main/resources&lt;/directory>
 *     &lt;filtering>true&lt;/filtering>
 *     &lt;includes>
 *       &lt;include>jsp/inc/taglib.jsp&lt;/include>
 *     &lt;/includes>
 *   &lt;/resource>
 * &lt;/resources>
 * 
 * &lt;plugins>
 *   &lt;plugin>
 *     &lt;groupId>net.gazhi.delonix&lt;/groupId>
 *     &lt;artifactId>delonix-mvn-plugin&lt;/artifactId>
 *     &lt;executions>
 *       &lt;execution>
 *         &lt;phase>initialize&lt;/phase>
 *         &lt;goals>
 *           &lt;goal>set-static-last-modified-property&lt;/goal>
 *         &lt;/goals>
 *       &lt;/execution>
 *     &lt;/executions>
 *   &lt;/plugin>
 * &lt;/plugins>
 * 
 * &lt;/build>
 * </pre>
 * 
 * <b>示例 layout.jsp</b><br>
 * <br>
 * &lt;script src=
 * "${pageContext.request.contextPath}/static/style.css?t=${static_last_modified}"
 * >&lt;/script><br>
 * <br>
 * 
 * @author Jeffrey Lin
 *
 */
@Mojo(name = "set-static-last-modified-property")
public class SetStaticLastModifiedPropertyMojo extends AbstractMojo {

	@Parameter(defaultValue = "${project}")
	private MavenProject project;

	@Parameter(defaultValue = "${basedir}")
	private String basedir;

	@Parameter(defaultValue = "src/main/webapp/static")
	private String staticFile;

	public void execute() throws MojoExecutionException {
		File file = new File(basedir + "/" + staticFile);
		long lastModified = maxLastModifiedOf(file);
		project.getProperties().setProperty("static_last_modified", String.valueOf(lastModified));

		getLog().info("########    Setting property:    ########");
		getLog().info("static_last_modified = " + lastModified + " [" + new Timestamp(lastModified) + "]");
		getLog().info("");

		Properties props = System.getProperties();
		getLog().info("java.version=" + props.getProperty("java.version"));
		getLog().info("os.name=" + props.getProperty("os.name"));
		getLog().info("os.arch=" + props.getProperty("os.arch"));
		getLog().info("os.version=" + props.getProperty("os.version"));
		getLog().info("user.name=" + props.getProperty("user.name"));
		getLog().info("user.home=" + props.getProperty("user.home"));
		getLog().info("user.dir=" + props.getProperty("user.dir"));
		getLog().info("");
		getLog().info("");
		printEnvVars();
		getLog().info("");
		getLog().info("");
	}

	private long maxLastModifiedOf(File file) {
		long result = 0;
		if (file.exists()) {
			if (file.isFile()) {
				result = file.lastModified();
			} else {
				for (File child : file.listFiles()) {
					long lastModified = maxLastModifiedOf(child);
					result = lastModified > result ? lastModified : result;
				}
			}
		}
		return result;
	}

	public void printEnvVars() {
		try {
			Process p = null;
			Runtime r = Runtime.getRuntime();
			String OS = System.getProperty("os.name").toLowerCase();
			if (OS.indexOf("windows 9") > -1) {
				p = r.exec("command.com /c set");
			} else if ((OS.indexOf("nt") > -1) || (OS.indexOf("windows 20") > -1) || (OS.indexOf("windows xp") > -1)|| (OS.indexOf("windows 7") > -1)) {
				// thanks to JuanFran for the xp fix!
				p = r.exec("cmd.exe /c set");
			} else {
				// our last hope, we assume Unix (thanks to H. Ware for the fix)
				p = r.exec("env");
			}
			BufferedReader br = new BufferedReader(new InputStreamReader(p.getInputStream()));
			String line;
			while ((line = br.readLine()) != null) {
				getLog().info(line);
			}
		} catch (Exception e) {
			throw new RuntimeException(e);
		}
	}

}
